(defpackage :input-widget
  (:use :cl)
  (:export :input-add
	   :input-backspace
           :input-string
           :input-submit
           :input-step
           :input-max
           :input-min-width
           :input
           :base-input))
(in-package :input-widget)

(defclass base-input ()
  ((max :initform nil :initarg :max :accessor input-max)
   (min-width :initform 150 :initarg :min-width :accessor input-min-width)))

(defgeneric input-add (widget thing))
(defgeneric input-backspace (widget))
(defgeneric input-string (widget))
(defgeneric input-submit (widget))

;; A basic input implementation

(defclass input (base-input gwee:text-area)
  ()
  (:default-initargs
   :border-color (gwee:gray 200)
    :wrap-p nil
    :font (gwee:open-font "serif.ttf" 48)
    :data ""
    :foreground (gwee:color 0 0 255)
    :horizontal-justification :center
    :vertical-justification :center
    :width 150))

(defun recenter (widget)
  (setf (gwee:view-width widget) (max (input-min-width widget)
				      (+ (sdl:get-font-size (gwee:view-data widget) :size :w :font (gwee:view-font widget)) 25))
	(gwee:view-needs-sync-p (gwee:view-parent widget)) t))

(defmethod input-backspace ((widget input))
  (with-slots ((data gwee::data)) widget
    (when (plusp (length data))
      (setf data (subseq data 0 (1- (length data))))
      (recenter widget))))

(defmethod input-add ((widget input) thing)
  (when (or (not (input-max widget))
            (< (length (gwee:view-data widget))
               (input-max widget)))
    (setf thing (typecase thing
                  (character (string thing))
                  (string thing)
                  (t (prin1-to-string thing)))
          (gwee:view-data widget) (concatenate 'string
                                               (gwee:view-data widget)
                                               thing))
    (recenter widget)))

(defmethod input-string ((widget input))
  (gwee:view-data widget))

(defmethod input-submit ((widget input))
  (values t (input-string widget)))
